package cn.iocoder.yudao.module.mqtt.framework.mqtt;

import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationEvent;
import org.springframework.context.ApplicationListener;
import org.springframework.integration.mqtt.event.MqttConnectionFailedEvent;
import org.springframework.integration.mqtt.event.MqttSubscribedEvent;
import org.springframework.stereotype.Component;

/**
 * Spring Integration MQTT事件监听器
 * 用于监听MQTT连接状态变化事件
 *
 * @author 芋道源码
 */
@Slf4j
@Component
public class MqttIntegrationEventListener implements ApplicationListener<ApplicationEvent> {

    @Autowired
    private MqttConnectionListener mqttConnectionListener;

    @Override
    public void onApplicationEvent(ApplicationEvent event) {
        // 记录所有MQTT相关事件
        if (event.getClass().getSimpleName().contains("Mqtt")) {
            log.info("=== 捕获到MQTT事件 ===");
            log.info("事件类型: {}", event.getClass().getSimpleName());
            log.info("事件时间: {}", java.time.LocalDateTime.now());
            log.info("事件源: {}", event.getSource());
            log.info("=====================");
        }
        
        if (event instanceof MqttConnectionFailedEvent) {
            handleConnectionFailedEvent((MqttConnectionFailedEvent) event);
        } else if (event instanceof MqttSubscribedEvent) {
            handleSubscribedEvent((MqttSubscribedEvent) event);
        } else if (event.getClass().getSimpleName().contains("Lost") || 
                   event.getClass().getSimpleName().contains("Disconnect")) {
            // 处理连接丢失相关事件
            handleConnectionLostEvent(event);
        }
    }

    /**
     * 处理连接丢失事件
     */
    private void handleConnectionLostEvent(ApplicationEvent event) {
        log.error("=== Spring Integration MQTT连接丢失事件 ===");
        log.error("事件类型: {}", event.getClass().getSimpleName());
        log.error("事件时间: {}", java.time.LocalDateTime.now());
        log.error("事件源: {}", event.getSource());
        log.error("=========================================");
        
        // 尝试从事件源中提取客户端ID
        String clientId = extractClientIdFromEvent(event);
        if (clientId != null) {
            log.error("从事件中提取的客户端ID: {}", clientId);
            mqttConnectionListener.handleConnectionLost(clientId);
        } else {
            log.error("无法从事件中提取客户端ID");
        }
    }

    /**
     * 处理连接失败事件
     */
    private void handleConnectionFailedEvent(MqttConnectionFailedEvent event) {
        log.error("=== Spring Integration MQTT连接失败事件 ===");
        log.error("事件时间: {}", java.time.LocalDateTime.now());
        log.error("事件源: {}", event.getSource());
        log.error("异常信息: {}", event.getCause() != null ? event.getCause().getMessage() : "未知");
        log.error("异常堆栈: ", event.getCause());
        log.error("=========================================");
    }

    /**
     * 处理订阅成功事件
     */
    private void handleSubscribedEvent(MqttSubscribedEvent event) {
        log.info("=== Spring Integration MQTT订阅成功事件 ===");
        log.info("事件时间: {}", java.time.LocalDateTime.now());
        log.info("事件源: {}", event.getSource());
        log.info("===============================");
    }

    /**
     * 从事件中提取客户端ID
     */
    private String extractClientIdFromEvent(ApplicationEvent event) {
        try {
            // 尝试从事件源中提取客户端ID
            Object source = event.getSource();
            if (source != null) {
                String sourceStr = source.toString();
                log.debug("事件源字符串: {}", sourceStr);
                
                // 查找包含客户端ID的模式
                if (sourceStr.contains("sub_client_id_")) {
                    // 提取客户端ID
                    int startIndex = sourceStr.indexOf("sub_client_id_");
                    int endIndex = sourceStr.indexOf(" ", startIndex);
                    if (endIndex == -1) {
                        endIndex = sourceStr.length();
                    }
                    return sourceStr.substring(startIndex, endIndex);
                } else if (sourceStr.contains("pub_client_id_")) {
                    // 提取发布客户端ID
                    int startIndex = sourceStr.indexOf("pub_client_id_");
                    int endIndex = sourceStr.indexOf(" ", startIndex);
                    if (endIndex == -1) {
                        endIndex = sourceStr.length();
                    }
                    return sourceStr.substring(startIndex, endIndex);
                }
            }
        } catch (Exception e) {
            log.warn("从事件中提取客户端ID失败", e);
        }
        return null;
    }
} 